home *** CD-ROM | disk | FTP | other *** search
-
- /*'Liner Version 1.32. Written by Dave Schreiber */
- /*©1988, 1989 Dave Schreiber. All Rights Reserved. */
- /*1.32 completed Monday, October 31, 1989 */
- /*1.31 completed Friday, October 6, 1989 */
- /*1.3 completed Saturday, February 25, 1989 */
- /*1.2 completed Friday, November 11, 1988 */
- /*1.1 completed Friday, October 14, 1988 */
- /*1.0 completed Friday, September 9, 1988 */
-
- /*Compiled with Lattice C V5.02 */
- /*To compile: 1> lc -cw -j30 -L+YAFR:YAFR.o 'Liner */
- /*You must assign YAFR: to the directory where YAFR.o is stored. */
- /*You must also assign LINER: to the directory where the 'Liner source */
- /*is located. */
-
- /*'Liner is an outliner, with up to six levels of depth, and up to */
- /*26 items per level (each isolated section). It has both clipboard and */
- /*non-clipboard support of CUT, COPY, and PASTE. It can output files */
- /*in its own format, or in ASCII (to disk or printer). It can read files*/
- /*in its own format only. It uses dynamic memory allocation to allow */
- /*an infinite number of items (memory providing).*/
-
- /*Amiga features of note that are used: */
- /*console device, disk i/o, printer i/o, clipboard i/o */
-
- /*Intuition objects (screen, windows, gadgets, menus, etc.) generated by */
- /*PowerWindows Version 2.0*/
-
- /*V1.1 corrects some bugs, doubles the number of characters available */
- /*for filenames, and improves PrintItemList() so that it doesn't always */
- /*print the entire item list*/
-
- /*1.2 allows the toggling between 640x200 & 640x400 screens and the */
- /*choice of the order that levels appear in, has a completely reworked */
- /*About... window, lets the user change the level of all the items */
- /*in a highlighted block, and now displays the current filename */
- /*in the title bar.*/
-
- /*1.3 adds support for user-selected keymaps, and now prints an asterisk */
- /*in the title bar if an outline has been edited but not saved. It also */
- /*includes my very own file requester, YAFR (Yet Another File Requester) */
- /*based in principal upon Charlie Heath's, but with a lot more buttons. */
-
- /*1.31 changes the default device where files are located from DF0: to */
- /*the current directory */
-
- /*1.32 fixed a bug that kept the screen from updating properly after a */
- /*paste. Also uses YAFR V1.1 */
-
- #include <exec/types.h>
- #include <exec/exec.h>
- #include <intuition/intuition.h>
- #include <devices/console.h>
- #include <devices/clipboard.h>
- #include <libraries/dos.h>
- #include <libraries/dosextens.h>
- #include <devices/inputevent.h>
- #include <devices/keymap.h>
- #include <math.h>
-
- struct IntuitionBase *IntuitionBase;
- struct GfxBase *GfxBase;
- ULONG DosBase;
-
- struct IOStdReq *consoleWriteMsg,*consoleReadMsg;
- struct Port *consoleWritePort,*consoleReadPort;
- struct IOClipReq ClipboardIO;
- struct MsgPort clipboardMsgPort;
- struct Process *ThisProc;
-
- struct LineItem /*'Liner structure definition*/
- {
- struct LineItem *NextItem,*PrevItem;
- UBYTE Level,ItemNumber;
- char Text[80];
- };
-
- extern struct LineItem *InsertItem(),*FindNext(),*FindPrev();
-
-
- struct Screen *Screen;
- struct Window *Window,*AboutWindow;
- struct KeyMap keymap;
- #define Rp Window->RPort;
- #define CSI 0x09b
- #define SEMI 0x03b
- #define NEWPAGE 0x0c
- #define CLOSECHAR 0x05c
- #define SCRNHEIGHT RowsInScreen
- #define REQUESTERCHARS 57
- APTR ConsoleDevice;
- struct LineItem *CharItem,*StartIItem,*EndIItem,*ClipStart,*ClipEnd;
- int ButtonState,PtrX,PtrY,LastX,LastY,InvsMode,StartChar,EndChar,InvY,EndIY;
- int BLastX,BLastY,ClipMode,ErrorInTitle=FALSE;
- UBYTE Laced,RowsInScreen,StartingLevel,Modified;
- char Indent=0;
- char DoubleSpc=FALSE;
- char FileName[150+33],SDirName[150],SFileName[33],SExt[18];
- char PDName[150+33],PDirName[150],PFileName[33],PExt[18];
-
- char ScreenTitle[] = {" 'Liner V1.32: "};
-
- #define UP 0
- #define DOWN 1
- #define NOINV 0
- #define LINE_PENDING 1
- #define LINE_FWD 2
- #define LINE_BACK 3
-
- #define BLOCK_PENDING -1
- #define BLOCK_DOWN -2
- #define BLOCK_UP -3
-
- UBYTE OLCPos[6][6]=
- {
- {9,13,17,21,25,29},
- {6,10,14,18,22,26},
- {6,10,14,18,22,26},
- {6,10,14,18,22,26},
- {6,10,14,18,22,26},
- {6,10,14,18,22,26}
- };
-
- /*Some macros*/
- #define PERPOS(x) OLCPos[StartingLevel][x]-3
- #define MinX(LI) OLCPos[StartingLevel][(LI->Level)-1]
- #define MaxX(LI) OLCPos[StartingLevel][(LI->Level)-1]+strlen(LI->Text)
- #define MaxLen(Level) 79-OLCPos[StartingLevel][Level-1]
- #define PosInText(Level) CurX-OLCPos[StartingLevel][Level-1]
- #define RealLevel(LI) (LI->Level+StartingLevel > 6) ? (LI->Level+StartingLevel-7) : (LI->Level+StartingLevel)
- /* ^^^ == get level when StartingLevel != 0 */
- /*Pointers to various LineItems*/
- struct LineItem *FirstItem,*LastItem,*CurrentItem,*FirstScrnItem,*ScrnBtm;
- int CurX,CurY,DispRows;
-
- /*Outline characters*/
- char *OutLineChars[6][26]=
- {
- {
- {"I."},{"II."},{"III."},{"IV."},{"V."},{"VI."},{"VII."},{"VIII."},
- {"IX."},{"X."},{"XI."},{"XII."},{"XIII."},{"XIV."},{"XV."},{"XVI."},
- {"XVII."},{"XVIII."},{"XIX."},{"XX."},{"XXI."},{"XXII."},{"XXIII."},
- {"XXIV."},{"XXV."},{"XXVI."}
- },
-
- {
- {"A."},{"B."},{"C."},{"D."},{"E."},{"F."},{"G."},{"H."},{"I."},
- {"J."},{"K."},{"L."},{"M."},{"N."},{"O."},{"P."},{"Q."},{"R."},
- {"S."},{"T."},{"U."},{"V."},{"W."},{"X."},{"Y."},{"Z."}
- },
-
- {
- {"1."},{"2."},{"3."},{"4."},{"5."},{"6."},{"7."},{"8."},{"9."},
- {"10."},{"11."},{"12."},{"13."},{"14."},{"15."},{"16."},{"17."},
- {"18."},{"19."},{"20."},{"21."},{"22."},{"23."},{"24."},{"25."},
- {"26."}
- },
-
- {
- {"a."},{"b."},{"c."},{"d."},{"e."},{"f."},{"g."},{"h."},{"i."},
- {"j."},{"k."},{"l."},{"m."},{"n."},{"o."},{"p."},{"q."},{"r."},
- {"s."},{"t."},{"u."},{"v."},{"w."},{"x."},{"y."},{"z."}
- },
-
- {
- {"1)"},{"2)"},{"3)"},{"4)"},{"5)"},{"6)"},{"7)"},{"8)"},{"9)"},
- {"10)"},{"11)"},{"12)"},{"13)"},{"14)"},{"15)"},{"16)"},{"17)"},
- {"18)"},{"19)"},{"20)"},{"21)"},{"22)"},{"23)"},{"24)"},{"25)"},
- {"26)"}
- },
-
- {
- {"a)"},{"b)"},{"c)"},{"d)"},{"e)"},{"f)"},{"g)"},{"h)"},{"i)"},
- {"j)"},{"k)"},{"l)"},{"m)"},{"n)"},{"o)"},{"p)"},{"q)"},{"r)"},
- {"s)"},{"t)"},{"u)"},{"v)"},{"w)"},{"x)"},{"y)"},{"z)"}
- },
- };
-
- /*The position of each special character in the array below*/
- int SCPos[]=
- {0,1,4,5,9,13,14,16,17,18,19,20,21,23,25,27,29};
-
- /*Special characters (TAB, RETURN, etc.)*/
- char SpecChars[]=
- {
- 32,
- 8,CSI,'P',
- 0,
- 0x0D,0x0A,CSI,'L',
- 0x0D,0x0A,CSI,'L',
- 0,
- CSI,'P',
- 0,
- 0,
- 0,
- 0,
- 0,
- CSI,'A',
- CSI,'B',
- CSI,'C',
- CSI,'D'
- };
-
- /*All the other little components of 'Liner*/
- #include <liner:mouse.h>
- #include <liner:Windows.h>
- #include <liner:menu.h>
- #include <liner:disk.h>
- #include <liner:sure.h>
- #include <liner:clip.h>
-
- _main()
- {
- ULONG Class;
- USHORT Code,Qualifier;
- APTR IAddress;
- SHORT MouseX,MouseY;
- int Seconds,Micros;
- struct IntuiMessage *Message;
-
- char Buffer[200];
- Buffer[0]=NULL;
- FileName[0]=SFileName[0]=SExt[0]=NULL;
- strcpy(SDirName,"");
- strcpy(PDirName,"");
- PDName[0]=PFileName[0]=PExt[0]=NULL;
- Laced=FALSE; /*Not interlaced*/
- Modified=FALSE; /*No modifications, yet*/
- StartingLevel=0;
-
- /*Open all the libraries*/
- IntuitionBase=(struct IntuitionBase *)OpenLibrary("intuition.library",1);
- if(IntuitionBase==NULL)
- exit(10);
-
- GfxBase=(struct GfxBase *)OpenLibrary("graphics.library",1);
- if(GfxBase==NULL)
- exit(20);
-
- DosBase=OpenLibrary("dos.library",1);
- if(DosBase==NULL)
- exit(30);
-
- RowsInScreen=23;
- ThisProc=(struct Process *)FindTask(NULL); /*Get 'Liner's process structure*/
- OpenGraphics(); /*Open screen, window, etc.*/
- SetupClipboard(); /*Open the clipboard*/
-
- /*Setup various system variable*/
- DispRows=1;
- PtrX=PtrY=LastX=LastY=1;
- ButtonState=UP;
- InvsMode=ClipMode=NOINV;
- FirstItem=LastItem=FirstScrnItem=CurrentItem=(struct LineItem *)
- InsertItem(NULL,NULL);
- FirstItem->Level=1;
- FirstItem->ItemNumber=0;
- PrintItemList(FirstItem,1);
- PlotCursor(MinX(CurrentItem),1);
- FileName[0]=PDName[0]=NULL;
-
- for(;;) /*The main loop!*/
- {
- Wait(1<<Window->UserPort->mp_SigBit); /*Wait for an event*/
- while((Message=(struct IntuiMessage *) /*Get the message*/
- GetMsg(Window->UserPort))!=NULL)
- { /*Get the message's information*/
- Class=Message->Class;
- Code=Message->Code;
- Qualifier=Message->Qualifier;
- MouseX=Message->MouseX;
- MouseY=Message->MouseY;
- Seconds=Message->Seconds;
- Micros=Message->Micros;
-
- IAddress=(APTR)Message->IAddress;
-
- ReplyMsg(Message); /*Reply to the message*/
-
- /*Decode the message*/
- if(HandleIDCMP(Class,Code,Qualifier,MouseX,MouseY,IAddress,
- Buffer,Seconds,Micros))
- { /*If the message was a keypress*/
- InsertChar(CurrentItem->Text,Buffer[2], /*Print the letter*/
- PosInText(CurrentItem->Level)); /*onto the screen*/
- CurX++;
- WriteConsole(Buffer,-1);
- }
- }
- }
- }
-
- WriteConsole(Buffer,Length) /*Write a string to the console*/
- char *Buffer;
- int Length;
- {
- consoleWriteMsg->io_Command=CMD_WRITE;
- consoleWriteMsg->io_Data=(char *)Buffer;
- consoleWriteMsg->io_Length=Length;
- DoIO(consoleWriteMsg);
- }
-
- /*Decode an IDCMP message*/
- HandleIDCMP(Class,Code,Qualifier,MouseX,MouseY,IAddress,Buffer,Secs,Micros)
- ULONG Class;
- USHORT Code,Qualifier;
- APTR IAddress;
- SHORT MouseX,MouseY;
- int Secs,Micros;
- char *Buffer;
- {
- struct MenuItem *item;
- struct InputEvent KeyEvent;
- struct LineItem *WorkingItem;
- int TempX,TempY;
- Buffer[0]=CSI;
- Buffer[1]=0x40;
- Buffer[2]=NULL;
- switch(Class)
- {
- case MENUPICK: /*There was a menu selection*/
- if(ErrorInTitle)
- TitleErrorCancel();
- while(Code != MENUNULL)
- {
- item=(struct MenuItem *)ItemAddress(&Menu1,Code);
- HandleEvent(item);
- Code=item->NextSelect;
- }
- case MOUSEBUTTONS: /*The left mouse button was pushed*/
- if(Code==SELECTDOWN)
- HandleButton(Secs,Micros);
- break;
- case MOUSEMOVE: /*The mouse was moved*/
- MovedMouse(MouseX,MouseY);
- break;
- /*A key was pressed*/
- case RAWKEY: /*By using IDCMP RAWKEY as input, and the*/
- if(Code & 0x80) /*console for output, we can both get input*/
- return(FALSE); /*and IDCMP messsages without having to try*/
- if(ErrorInTitle) /*and decode ASCII console messages*/
- TitleErrorCancel(); /*(IDCMP structures are MUCH easier)*/
- if((Code < 0x41) || (0x5a <= Code && Code <= 0x5e) ||
- (Code==0x4a))
- { /*^^^==All the RAWKEY codes that represent ASCII symbols*/
- CheckModified();
- KeyEvent.ie_NextEvent=NULL; /*Create a fake input event*/
- KeyEvent.ie_Class=IECLASS_RAWKEY; /*for RawKeyConvert() to */
- KeyEvent.ie_SubClass=NULL; /*munch on. Using RawKeyConvert()*/
- KeyEvent.ie_Code=Code; /*insures that the current keymap*/
- KeyEvent.ie_Qualifier=Qualifier; /*is used*/
- RawKeyConvert(&KeyEvent,&Buffer[2],200,&keymap),ConsoleDevice;
- Buffer[3]=NULL; /* ^^^ == RAWKEY to ASCII*/
-
- if(InvsMode < NOINV) /*If a block of lines was highlighted*/
- { /*when a key was pressed, cancel the*/
- EndBlockInvs(); /*highlight*/
- return(FALSE);
- }
- /*If a key was pressed when TEXT was*/
- if(InvsMode) /*highlighted, delete the text & replace*/
- DelTextBlock(); /*it with the letter pressed*/
-
- /*If the current line isn't full*/
- if(strlen(CurrentItem->Text)<MaxLen(CurrentItem->Level))
- return(TRUE); /*OK to print the character*/
- else
- return(FALSE); /*Otherwise not*/
- }
- else
- switch(Code) /*Handle all the "special" characters*/
- {
- case 0x4d: /*Move cursor down one*/
- CancelInvs();
- if(Qualifier & 3) /*Handle SHIFT-DOWN*/
- WholeScreenDown();
- else if(Qualifier & 8) /*Handle CTRL-DOWN*/
- JumpToBottom();
- else
- CursorDown();
- break;
- case 0x4c: /*Move cursor up one*/
- CancelInvs();
- if(Qualifier & 3) /*Check for shift*/
- WholeScreenUp();
- else if(Qualifier & 8) /*Check for control*/
- JumpToTop();
- else
- CursorUp();
- break;
- case 0x4e: /*Move cursor one to the right*/
- CancelInvs();
- if(CurX >= MaxX(CurrentItem))
- {
- TempX=CurX;
- CurX=1;
- if(!CursorDown())
- CurX=TempX;
- }
- else
- if(Qualifier & 3) /*Handle SHIFT-cursor-right*/
- PlotCursor(MaxX(CurrentItem),CurY);
- else
- PlotCursor(CurX+1,CurY);
- break;
- case 0x4f: /*Move cursor one to the left*/
- CancelInvs();
- if(CurX <= MinX(CurrentItem))
- {
- TempX=CurX;
- CurX=100;
- if(!CursorUp())
- CurX=TempX;
- }
- else
- if(Qualifier & 3) /*Handle SHIFT-cursor-left*/
- PlotCursor(MinX(CurrentItem),CurY);
- else
- PlotCursor(CurX-1,CurY);
- break;
- case 0x41: /*Backspace over a character*/
- CheckModified();
- if(DelInvs()) /*If something is highlighted*/
- break; /*delete it*/
-
- /*Delete the character, if not at the beginning of the line...*/
- if(CurX>MinX(CurrentItem))
- {
- strcpy(Buffer,&SpecChars[SCPos[1]]);
- Buffer[SCPos[2]-SCPos[1]]=NULL;
- DeleteChar(CurrentItem->Text,
- PosInText(CurrentItem->Level)-1);
- WriteConsole(Buffer,-1);
- CurX--;
- }
- else /*otherwise, delete the line*/
- if(CurrentItem->PrevItem != NULL &&
- strlen(CurrentItem->Text)==0)
- {
- DelBlock(CurrentItem,CurrentItem,CurY,CurY);
- if(CurrentItem != LastItem)
- CursorUp();
- PlotCursor(MaxX(CurrentItem),CurY);
- }
- break;
- case 0x46: /*Delete a character*/
- CheckModified();
- if(DelInvs())
- break;
-
- if(CurX<MaxX(CurrentItem))
- {
- strcpy(Buffer,&SpecChars[SCPos[6]]);
- Buffer[SCPos[7]-SCPos[6]]=NULL;
- DeleteChar(CurrentItem->Text,
- PosInText(CurrentItem->Level));
- WriteConsole(Buffer,-1);
- }
- break;
- case 0x42: /*TAB (in or out)*/
- CheckModified();
- if(InvsMode < NOINV) /*Block highlighted*/
- if(Qualifier & 3)
- if(InvsMode==BLOCK_DOWN)
- PullOutBlock(StartIItem,EndIItem,InvY);
- else
- PullOutBlock(EndIItem,StartIItem,EndIY);
- else
- if(InvsMode==BLOCK_DOWN)
- PushInBlock(StartIItem,EndIItem,InvY);
- else
- PushInBlock(EndIItem,StartIItem,EndIY);
- else
- {
- if(CancelInvs())
- return(FALSE);
- TempY=CurY;
- PlotCursor(1,TempY);
- if(Qualifier & 3) /*TAB out (shift pressed)*/
- PullOut(CurrentItem);
- else
- PushIn(CurrentItem); /*TAB in*/
- PlotCursor(MinX(CurrentItem),TempY);
- }
- break;
- case 0x43: /*Return & Enter */
- case 0x44: /*Insert a line*/
- CheckModified();
- if(CancelInvs())
- return(FALSE);
- if(CurX < MaxX(CurrentItem))
- if(!CursorUp())
- {
- InsertLineAtTop();
- return(FALSE);
- }
- strcpy(Buffer,&SpecChars[SCPos[4]]);
- WriteConsole(Buffer,4);
- WorkingItem=(struct LineItem *)
- InsertItem(CurrentItem->NextItem,CurrentItem);
- WorkingItem->Level=CurrentItem->Level;
- if(CurrentItem->ItemNumber==25)
- WorkingItem->ItemNumber=0;
- else
- WorkingItem->ItemNumber=CurrentItem->ItemNumber+1;
- if(CurY==SCRNHEIGHT)
- {
- ScrnBtm=(struct LineItem *)WorkingItem;
- FirstScrnItem=(struct LineItem *)
- FirstScrnItem->NextItem;
- }
- else
- {
- CurY++;
- if(DispRows==SCRNHEIGHT)
- ScrnBtm=(struct LineItem *)ScrnBtm->PrevItem;
- else
- ++DispRows;
- }
- if(WorkingItem->NextItem==NULL)
- ScrnBtm=LastItem=(struct LineItem *)
- WorkingItem;
- AddItem(WorkingItem);
- TempY=CurY;
- RedrawOutlineChars(WorkingItem,WorkingItem->Level,0);
- CurrentItem=(struct LineItem *)WorkingItem;
- PlotCursor(MinX(CurrentItem),TempY);
- break;
- }
- return(FALSE);
- }
- return(FALSE);
-
- }
-
- /*Close everything*/
- CloseStuff()
- {
- FreeListMem(FirstItem,LastItem);
- if(ClipMode < NOINV)
- FreeListMem(ClipStart,ClipEnd);
-
- ShutDownClipboard();
- CloseGraphics();
-
- CloseLibrary(DosBase);
- CloseLibrary(GfxBase);
- CloseLibrary(IntuitionBase);
- exit(0);
- }
-
- Leave(err,why) /*If an error occured, tell user, close window & screen*/
- int err; /*& exit*/
- char *why;
- {
- TitleError(why);
- Delay(500); /*Give user 5 seconds to read error message*/
- exit(err);
- }
-
- PushIn(Item) /*Increase and redraw the level of an item*/
- struct LineItem *Item;
- {
- if(Push(Item))
- {
- RedrawOutlineChars(Item,Item->Level-1,Item->Level);
- return(TRUE);
- }
- else
- return(FALSE);
- }
-
- Push(Item) /*Increase the level of an item (I. to A., etc.)*/
- struct LineItem *Item;
- {
- if(Item->Level==6)
- return(FALSE);
-
- RemItem(Item);
- Item->Level++; /*Increase the level and chop off excess text if it*/
- Item->Text[MaxLen(Item->Level)]=NULL; /*would go off the line*/
- AddItem(Item);
- PrintItem(Item);
-
- return(TRUE);
- }
-
- PullOut(Item) /*Decrease the level of an item and redraw*/
- struct LineItem *Item;
- {
- if(Pull(Item))
- {
- RedrawOutlineChars(Item,Item->Level+1,Item->Level);
- return(TRUE);
- }
- else
- return(FALSE);
- }
-
- Pull(Item) /*Decrease the level of an item (a. to 1., etc.)*/
- struct LineItem *Item;
- {
- if(Item->Level==1)
- return(FALSE);
-
- RemItem(Item);
- Item->Level--;
- AddItem(Item);
- AddItem(Item->NextItem);
- PrintItem(Item);
-
- return(TRUE);
- }
-
- PushInBlock(Start,End,YStart) /*Indent a reversed block*/
- struct LineItem *Start,*End;
- UBYTE YStart;
- {
- struct LineItem *Item;
- UBYTE OldX=CurX;
- UBYTE OldY=CurY;
- UBYTE Y=YStart;
-
- Item=(struct LineItem *)Start; /*Check to see if any items are as*/
- while(Item != End) /*pushed in as possible*/
- {
- if(Item->Level == 6)
- return(FALSE);
- Item=(struct LineItem *)Item->NextItem;
- }
-
- PlotCursor(1,Y);
- Item=(struct LineItem *)Start; /*Do first one*/
- Push(Item);
-
- while(Item != End) /*Loop until all pushed in*/
- {
- Item=(struct LineItem *)Item->NextItem;
- PlotCursor(1,++Y);
- Push(Item);
- }
-
- PlotCursor(1,++Y); /*Redraw outline characters*/
- RedrawOutlineChars(End->NextItem,6,5);
- PlotCursor(1,Y);
- RedrawOutlineChars(End->NextItem,4,3);
- PlotCursor(1,Y);
- RedrawOutlineChars(End->NextItem,2,1);
-
- PlotCursor(1,YStart);
- RvsBlock(Start,End);
- if(OldX < MinX(CurrentItem)) /*OldX might no longer be possible if*/
- PlotCursor(MinX(CurrentItem),OldY); /*CurrentItem was one pushed in*/
- else
- PlotCursor(OldX,OldY);
- }
-
- PullOutBlock(Start,End,YStart) /*Indent a reversed block*/
- struct LineItem *Start,*End;
- UBYTE YStart;
- {
- struct LineItem *Item;
- UBYTE OldX=CurX;
- UBYTE OldY=CurY;
- UBYTE Y=YStart;
-
- Item=(struct LineItem *)Start; /*Check to see if any items are as*/
- while(Item != End) /*pushed in as possible*/
- {
- if(Item->Level == 1)
- return(FALSE);
- Item=(struct LineItem *)Item->NextItem;
- }
-
- PlotCursor(1,Y);
- Item=(struct LineItem *)Start; /*Do first one*/
- Pull(Item);
-
- while(Item != End) /*Loop until all pushed in*/
- {
- Item=(struct LineItem *)Item->NextItem;
- PlotCursor(1,++Y);
- Pull(Item);
- }
- PlotCursor(1,++Y); /*Redraw outline characters*/
- RedrawOutlineChars(End->NextItem,6,5);
- PlotCursor(1,Y);
- RedrawOutlineChars(End->NextItem,4,3);
- PlotCursor(1,Y);
- RedrawOutlineChars(End->NextItem,2,1);
-
- PlotCursor(1,YStart);
- RvsBlock(Start,End);
- if(OldX > MaxX(CurrentItem)) /*OldX might no longer be possible if*/
- PlotCursor(MaxX(CurrentItem),OldY); /*CurrentItem was one pushed in*/
- else
- PlotCursor(OldX,OldY);
- }
-
- JumpToTop() /*Jump to top of outline*/
- {
- FirstScrnItem=CurrentItem=(struct LineItem *)FirstItem;
- PrintItemList(CurrentItem,1);
- PlotCursor(MinX(CurrentItem),1);
- }
-
- JumpToBottom() /*Jump to bottom of outline*/
- {
- struct LineItem *Item;
- int c;
-
- CurrentItem=(struct LineItem *)LastItem;
- for(c=0,Item=(struct LineItem *)LastItem;Item!=FirstItem &&
- c < SCRNHEIGHT-1;Item=(struct LineItem *)Item->PrevItem,c++);
- FirstScrnItem=(struct LineItem *)Item;
- PrintItemList(FirstScrnItem,1);
- PlotCursor(MinX(CurrentItem),DispRows);
- }
-
- PrintItemList(FrstItem,StartY) /*Prints a specified number of items*/
- struct LineItem *FrstItem;
- int StartY;
- {
- struct LineItem *CrntItem;
- int y;
- char Buffer[3];
-
- PlotCursor(1,StartY);
- CrntItem=(struct LineItem *)FrstItem;
- Buffer[0]=0x9b;
- Buffer[1]=0x4a;
- WriteConsole(Buffer,2);
-
- for(y=StartY;y<=SCRNHEIGHT && CrntItem!=NULL;y++)
- {
- PlotCursor(1,y);
- PrintItem(CrntItem);
- ScrnBtm=(struct LineItem *)CrntItem;
- CrntItem=(struct LineItem *)CrntItem->NextItem;
- }
- DispRows=y-1;
- }
-
- PrintItem(Item) /*Print an item at the current Y location*/
- struct LineItem *Item;
- {
- char ConsoleBuffer[100];
-
- ConsoleBuffer[0]=CSI;
- ConsoleBuffer[1]=0x4b;
- ConsoleBuffer[2]=NULL;
-
- GetOutlineChars(Item,ConsoleBuffer);
- strcat(ConsoleBuffer," ");
- strcat(ConsoleBuffer,Item->Text);
- WriteConsole(ConsoleBuffer,-1);
- }
-
- GetOutlineChars(Item,ConsoleBuffer) /*Get the outline chars (IX.,B.,etc.)*/
- struct LineItem *Item; /*for an item*/
- char *ConsoleBuffer;
- {
- int Level,StrLen,InsLen,c;
-
- Level=RealLevel(Item)-1;
- StrLen=strlen(OutLineChars[Level][(Item->ItemNumber)]);
- InsLen=PERPOS((Item->Level)-1)-StrLen;
- for(c=0;c<InsLen;c++)
- strcat(ConsoleBuffer," ");
-
- strcat(ConsoleBuffer,OutLineChars[Level][(Item->ItemNumber)]);
- }
-
- RedrawOutlineChars(Item,Hi,Lo) /*Redraw the outline characters */
- struct LineItem *Item; /*(Lo <= Changed level <= Hi)*/
- int Hi,Lo;
- {
- char Buffer[60];
- int x=1;
- int y,Level;
-
- Level=Item->Level;
-
- for(y=CurY;y<=SCRNHEIGHT & Item != NULL ;y++)
- {
- if(Lo == Item->Level || Hi == Item->Level)
- {
- PlotCursor(x,y);
- strcpy(Buffer,"");
- GetOutlineChars(Item,Buffer);
- WriteConsole(Buffer,-1);
- }
- Item=(struct LineItem *)Item->NextItem;
- }
- }
-
- PlotCursor(x,y) /*Plot the console cursor on the screen*/
- int x,y;
- {
- char Buffer[10];
- int len=1;
-
- Buffer[0]=CSI;
- len+=stci_d(&Buffer[1],y,9);
- Buffer[len]=0x3b;
- len+=stci_d(&Buffer[len+1],x,6);
- Buffer[len+1]=0x48;
- Buffer[len+2]=NULL;
- WriteConsole(Buffer,-1);
- CurX=x;
- CurY=y;
- }
-
- CursorUp() /*Move the cursor up (scroll screen, etc.)*/
- {
- char Buffer[20];
- int TempX;
-
- if(CurrentItem->PrevItem !=NULL)
- {
- if(CurrentItem==FirstScrnItem && CurrentItem != FirstItem)
- {
- strcpy(Buffer,&SpecChars[SCPos[0x0c]]);
- WriteConsole(Buffer,2);
- TempX=CurX;
- PlotCursor(1,1);
- PrintItem(CurrentItem->PrevItem);
- ++CurY;
- if(ScrnBtm==LastItem && DispRows < SCRNHEIGHT)
- ++DispRows;
- else
- ScrnBtm=(struct LineItem *)ScrnBtm->PrevItem;
- FirstScrnItem=(struct LineItem *)FirstScrnItem->PrevItem;
- CurX=TempX;
- InvY++;
- }
-
- if(CurX < MinX(CurrentItem->PrevItem))
- CurX=MinX(CurrentItem->PrevItem);
- else
- if(CurX > MaxX(CurrentItem->PrevItem))
- CurX=MaxX(CurrentItem->PrevItem);
- PlotCursor(CurX,CurY-1);
- CurrentItem=(struct LineItem *) CurrentItem->PrevItem;
- return(TRUE);
- }
- return(FALSE);
- }
-
- CursorDown() /*Move the cursor down (scroll screen, etc.)*/
- {
- char Buffer[20];
- int TempX;
-
- if(CurrentItem->NextItem != NULL)
- {
- if(CurrentItem==ScrnBtm && (CurrentItem->NextItem != NULL))
- {
- strcpy(Buffer,&SpecChars[SCPos[0x0d]]);
- WriteConsole(Buffer,2);
- TempX=CurX;
- PlotCursor(1,CurY);
- PrintItem(CurrentItem->NextItem);
- PlotCursor(TempX,CurY-1);
- ScrnBtm=(struct LineItem *)ScrnBtm->NextItem;
- FirstScrnItem=(struct LineItem *)FirstScrnItem->NextItem;
- InvY--;
- }
-
- if(CurX < MinX(CurrentItem->NextItem))
- CurX=MinX(CurrentItem->NextItem);
- else
- if(CurX > MaxX(CurrentItem->NextItem))
- CurX=MaxX(CurrentItem->NextItem);
- PlotCursor(CurX,CurY+1);
- CurrentItem=(struct LineItem *)CurrentItem->NextItem;
- return(TRUE);
- }
- return(FALSE);
- }
-
- InsertChar(Text,Character,Pos) /*Insert a char into an item*/
- char *Text,Character;
- int Pos;
- {
- int c;
-
- for(c=strlen(Text);c>=Pos;c--)
- Text[c+1]=Text[c];
- Text[Pos]=Character;
- }
-
- DeleteChar(Text,Pos) /*Delete a char in an item*/
- char *Text;
- int Pos;
- {
- int lim;
-
- for(lim=strlen(Text);Pos<lim;Pos++)
- Text[Pos]=Text[Pos+1];
- }
-
- /*Insert an item into the item list*/
- extern struct LineItem *InsertItem(NextItem,PrevItem)
- struct LineItem *NextItem,*PrevItem;
- {
- struct LineItem *Item;
-
- Item=(struct LineItem *)AllocMem(sizeof(struct LineItem),MEMF_CLEAR);
- if(Item==NULL)
- return(NULL);
-
- if(NextItem != NULL)
- {
- NextItem->PrevItem=(struct LineItem *)Item;
- Item->NextItem=(struct LineItem *)NextItem;
- }
-
- if(PrevItem != NULL)
- {
- PrevItem->NextItem=(struct LineItem *)Item;
- Item->PrevItem=(struct LineItem *)PrevItem;
- }
-
- return(Item);
- }
-
- RemItem(Item) /*Adjust the ItemNumbers for items after one is removed*/
- struct LineItem *Item;
- {
- int ItemNumber;
- struct LineItem *WorkingItem;
-
- if(Item==NULL)
- return(FALSE);
- if((WorkingItem=(struct LineItem *)FindPrev(Item))==NULL)
- ItemNumber=0;
- else
- ItemNumber=Item->ItemNumber;
-
- while((Item=(struct LineItem *)FindNext(Item))!=NULL)
- {
- if(ItemNumber==25)
- ItemNumber=0;
- Item->ItemNumber=ItemNumber++;
- }
- }
-
- AddItem(Item) /*Adjust the ItemNumbers after adding an item*/
- struct LineItem *Item;
- {
- int ItemNumber;
- struct LineItem *CrntItem;
-
- if((CrntItem=(struct LineItem *)FindPrev(Item))==NULL)
- ItemNumber=0;
- else
- ItemNumber=CrntItem->ItemNumber+1;
-
- do
- {
- if(ItemNumber==25)
- ItemNumber=0;
- Item->ItemNumber=ItemNumber++;
- Item=(struct LineItem *)FindNext(Item);
- }
- while(Item != NULL && Item->PrevItem->Level >= Item->Level);
- }
-
- extern struct LineItem *FindPrev(Item) /*Find the previous item of*/
- struct LineItem *Item; /*the same Level as Item*/
- {
- int Level;
-
- Level=Item->Level;
- Item=(struct LineItem *)Item->PrevItem;
-
- while(Item->Level > Level && Item !=NULL)
- Item=(struct LineItem *)Item->PrevItem;
-
- if(Item->Level < Level || Item == NULL)
- return(NULL);
- else
- return(Item);
- }
-
- extern struct LineItem *FindNext(Item) /*Find the next item of the same*/
- struct LineItem *Item; /*Level as Item*/
- {
- int Level;
-
- Level=Item->Level;
- Item=(struct LineItem *)Item->NextItem;
-
- while(Item->Level > Level && Item != NULL)
- Item=(struct LineItem *)Item->NextItem;
-
- if(Item->Level < Level)
- return(NULL);
- else
- return(Item);
- }
-
- InsertLineAtTop() /*Insert a line at the top of the list*/
- {
- struct LineItem *WorkingItem;
-
- WorkingItem=(struct LineItem *)
- InsertItem(FirstItem,NULL);
- WorkingItem->Level=1;
-
- FirstItem=(struct LineItem *)WorkingItem;
- AddItem(FirstItem);
- PlotCursor(1,1);
- RedrawOutlineChars(WorkingItem->NextItem,1,1);
- PlotCursor(MinX(CurrentItem),1);
- CursorUp();
- }
-
- WholeScreenDown() /*Scrolls down by an entire screen*/
- {
- struct LineItem *item;
- UBYTE c,X,Y;
-
- item=(struct LineItem *)ScrnBtm;
- if(item->NextItem == NULL) /*No lines after screen bottom?*/
- { /*Move to last line*/
- CurrentItem=(struct LineItem *)LastItem;
- PlotCursor(MinX(CurrentItem),DispRows);
- return(FALSE);
- }
- /*Get the first screen item*/
- item=FirstScrnItem=(struct LineItem *)item->NextItem;
- for(c=1;(c < CurY) && (item->NextItem != NULL);c++)
- item=(struct LineItem *)item->NextItem; /*Get item at old Y*/
-
- CurrentItem=(struct LineItem *)item; /*It is now the CurrentItem*/
- Y=c; /*In case CurY is no longer possible (23 lines down)*/
- /*If CurX's old position is no longer possible*/
- /*move the cursor to the nearest possible position*/
- if(CurX < MinX(CurrentItem))
- X=MinX(CurrentItem);
- else
- if(CurX > MaxX(CurrentItem))
- X=MaxX(CurrentItem);
- else
- X=CurX;
-
- for(c=1;(c < SCRNHEIGHT-CurY) && (item->NextItem != NULL);c++)
- item=(struct LineItem *)item->NextItem; /*Find screen bottom*/
- ScrnBtm=(struct LineItem *)item; /*Got it!*/
- DispRows=c; /*Get the number of lines*/
- PrintItemList(FirstScrnItem,1); /*Refresh the display*/
- PlotCursor(X,Y);
- return(TRUE); /*Done!*/
- }
-
-
- WholeScreenUp() /*Move up one screenfull of lines*/
- {
- struct LineItem *item;
- UBYTE c,X,Y;
-
- Y=CurY;
- item=(struct LineItem *)FirstScrnItem;
- if(item->PrevItem == NULL) /*At the top?*/
- { /*Move cursor to first line*/
- CurrentItem=(struct LineItem *)FirstItem;
- PlotCursor(MinX(CurrentItem),1);
- return(FALSE);
- }
- for(c=0;(c<SCRNHEIGHT) & (item->PrevItem != NULL);c++)
- item=(struct LineItem *)item->PrevItem;
- FirstScrnItem=(struct LineItem *)item;
- for(c=1;(c<CurY) && (item->NextItem != NULL);c++) /*Get new CurrentItem*/
- item=(struct LineItem *)item->NextItem;
- CurrentItem=(struct LineItem *)item;
-
- if(CurX < MinX(CurrentItem)) /*If CurX is no longer possible*/
- X=MinX(CurrentItem); /*get closest possible X*/
- else
- if(CurX > MaxX(CurrentItem))
- X=MaxX(CurrentItem);
- else
- X=CurX;
- for(;(c<SCRNHEIGHT) & (item->NextItem != NULL);c++)
- item=(struct LineItem *)item->NextItem; /*Get ScrnBtm*/
- ScrnBtm=(struct LineItem *)item;
- DispRows=c; /*Number of lines*/
- PrintItemList(FirstScrnItem,1); /*Refresh display*/
- PlotCursor(X,Y);
- return(TRUE); /*Done!*/
- }
-
- OpenGraphics() /*Open screen, window, etc.*/
- {
- /*Open screen (640x200x2)*/
- NewWindow.Screen=Screen=(struct Screen *)OpenScreen(&NewScreen);
- if(Screen==NULL)
- exit(40);
-
- /*Open backdrop window & make requestors open onto it*/
- if((ThisProc->pr_WindowPtr=Window=
- (struct Window *)OpenWindow(&NewWindow))==NULL)
- {
- CloseScreen(Screen);
- exit(50);
- }
- /*Install menus*/
- SetMenuStrip(Window,&Menu1);
-
- /*Setup the console.device*/
- consoleWritePort=(struct Port *)CreatePort("mycon.write",0);
- if(consoleWritePort==NULL)
- Leave(60,"Couldn't open console.device!");
-
- consoleWriteMsg=(struct IOStdReq *)CreateStdIO(consoleWritePort);
- if(consoleWriteMsg==NULL)
- Leave(70,"Couldn't open console.device!");
-
- consoleReadPort=(struct Port *)CreatePort("mycon.read",0);
- if(consoleReadPort==NULL)
- exit(60);
-
- consoleReadMsg=(struct IOStdReq *)CreateStdIO(consoleReadPort);
- if(consoleReadMsg==NULL)
- exit(70);
-
- consoleWriteMsg->io_Data=(struct Window *)Window; /*Attach console*/
- consoleWriteMsg->io_Length=sizeof(struct Window); /*device to window...*/
- OpenDevice("console.device",0,consoleWriteMsg,0); /*& open it*/
-
- ConsoleDevice=consoleReadMsg->io_Device=(APTR)consoleWriteMsg->io_Device;
- consoleReadMsg->io_Unit=consoleWriteMsg->io_Unit;
- consoleReadMsg->io_Command=CD_ASKKEYMAP;
- consoleReadMsg->io_Length=sizeof(struct KeyMap);
- consoleReadMsg->io_Data=&keymap;
- DoIO(consoleReadMsg);
- TitleErrorCancel();
- }
-
- CloseGraphics() /*Close the window, screen, etc.*/
- {
- CloseDevice(consoleWriteMsg);
- DeleteStdIO(consoleWriteMsg);
- DeleteStdIO(consoleReadMsg);
- DeletePort(consoleWritePort);
- DeletePort(consoleReadPort);
-
- ClearMenuStrip(Window);
- CloseWindow(Window);
- CloseScreen(Screen);
- }
-
-